package com.naiterui.ehp.bs.emr.service.impl;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.Date;
import java.util.List;
import java.util.stream.Collectors;

import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import com.naiterui.ehp.bp.bo.emr.MedicalRecordSettingBO;
import com.naiterui.ehp.bp.constants.MedicalRecordSettingEnum;
import com.naiterui.ehp.bp.support.exception.BaseExceptionCodes;
import com.naiterui.ehp.bp.support.exception.BusinessException;
import com.naiterui.ehp.bs.emr.entity.mysql.EmrMedicalRecordSetting;
import com.naiterui.ehp.bs.emr.exception.ExceptionCodes;
import com.naiterui.ehp.bs.emr.repository.mysql.IDrMedicalRecordSettingRepository;
import com.naiterui.ehp.bs.emr.service.IMedicalRecordSettingService;

import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.util.StrUtil;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;

/**
 * @author yangfuya
 * @since 2022/4/11
 */
@Slf4j
@Service
@RequiredArgsConstructor
public class MedicalRecordSettingServiceImpl implements IMedicalRecordSettingService {
    private final IDrMedicalRecordSettingRepository medicalRecordSettingRepository;

    @Override
    public List<MedicalRecordSettingBO> listByDoctorId(Long doctorId) {
        List<EmrMedicalRecordSetting> medicalRecordSettingList =
            this.medicalRecordSettingRepository.findAllByDoctorId(doctorId);
        // 如果该医生没有设置过病历设置则默认补充全部
        if (CollUtil.isEmpty(medicalRecordSettingList)) {
            return Arrays.asList(
                MedicalRecordSettingBO.builder().type(MedicalRecordSettingEnum.TYPE_CHIEF_COMPLAINT.getType())
                    .name(MedicalRecordSettingEnum.TYPE_CHIEF_COMPLAINT.getName())
                    .enabled(MedicalRecordSettingEnum.ENABLE_YES).build(),
                MedicalRecordSettingBO.builder().type(MedicalRecordSettingEnum.TYPE_HPI.getType())
                    .name(MedicalRecordSettingEnum.TYPE_HPI.getName()).enabled(MedicalRecordSettingEnum.ENABLE_YES)
                    .build(),
                MedicalRecordSettingBO.builder().type(MedicalRecordSettingEnum.TYPE_PAST_HISTORY.getType())
                    .name(MedicalRecordSettingEnum.TYPE_PAST_HISTORY.getName())
                    .enabled(MedicalRecordSettingEnum.ENABLE_YES).build(),
                MedicalRecordSettingBO.builder().type(MedicalRecordSettingEnum.TYPE_ALLERGIC_HISTOR.getType())
                    .name(MedicalRecordSettingEnum.TYPE_ALLERGIC_HISTOR.getName())
                    .enabled(MedicalRecordSettingEnum.ENABLE_YES).build(),
                MedicalRecordSettingBO.builder().type(MedicalRecordSettingEnum.TYPE_FAMILY_HISTORY.getType())
                    .name(MedicalRecordSettingEnum.TYPE_FAMILY_HISTORY.getName())
                    .enabled(MedicalRecordSettingEnum.ENABLE_YES).build(),
                MedicalRecordSettingBO.builder().type(MedicalRecordSettingEnum.TYPE_HMMC.getType())
                    .name(MedicalRecordSettingEnum.TYPE_HMMC.getName()).enabled(MedicalRecordSettingEnum.ENABLE_YES)
                    .build(),
                MedicalRecordSettingBO.builder().type(MedicalRecordSettingEnum.TYPE_INSPECTION_INDEX.getType())
                    .name(MedicalRecordSettingEnum.TYPE_INSPECTION_INDEX.getName())
                    .enabled(MedicalRecordSettingEnum.ENABLE_YES).build(),
                MedicalRecordSettingBO.builder().type(MedicalRecordSettingEnum.TYPE_DIAGNOSIS.getType())
                    .name(MedicalRecordSettingEnum.TYPE_DIAGNOSIS.getName())
                    .enabled(MedicalRecordSettingEnum.ENABLE_YES).build(),
                MedicalRecordSettingBO.builder().type(MedicalRecordSettingEnum.TYPE_TREATMENT_OPINION.getType())
                    .name(MedicalRecordSettingEnum.TYPE_TREATMENT_OPINION.getName())
                    .enabled(MedicalRecordSettingEnum.ENABLE_YES).build());
        }
        return medicalRecordSettingList.stream()
            .map(m -> MedicalRecordSettingBO.builder().type(m.getType()).name(m.getName()).enabled(m.getEnabled())
                .build())
            .collect(Collectors.toList());
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void edit(Long doctorId, String typeStr) throws BusinessException {
        if (StrUtil.isEmpty(typeStr)) {
            throw new BusinessException(BaseExceptionCodes.PARAM_ERROR);
        }
        String[] typeArr = typeStr.split(",");
        // 主诉、诊断、治疗已经不可关闭
        if (!Arrays.asList(typeArr).contains(MedicalRecordSettingEnum.TYPE_CHIEF_COMPLAINT.getType().toString())) {
            throw new BusinessException(ExceptionCodes.MEDICAL_RECORD_SETTING_CHIEF_COMPLAINT_NOT_CLOSE);
        }
        if (!Arrays.asList(typeArr).contains(MedicalRecordSettingEnum.TYPE_DIAGNOSIS.getType().toString())) {
            throw new BusinessException(ExceptionCodes.MEDICAL_RECORD_SETTING_CHIEF_DIAGNOSIS_NOT_CLOSE);
        }
        if (!Arrays.asList(typeArr).contains(MedicalRecordSettingEnum.TYPE_TREATMENT_OPINION.getType().toString())) {
            throw new BusinessException(ExceptionCodes.MEDICAL_RECORD_SETTING_CHIEF_TREATMENT_OPINION_NOT_CLOSE);
        }
        // 先删除再新增
        this.medicalRecordSettingRepository.deleteAllByDoctorId(doctorId);
        // 处理医生设置项
        List<EmrMedicalRecordSetting> medicalRecordSettingList = new ArrayList<>();
        MedicalRecordSettingEnum[] medicalRecordSettingEnums = MedicalRecordSettingEnum.class.getEnumConstants();
        EmrMedicalRecordSetting emrMedicalRecordSetting;
        for (MedicalRecordSettingEnum e : medicalRecordSettingEnums) {
            emrMedicalRecordSetting = new EmrMedicalRecordSetting();
            Integer type = e.getType();
            emrMedicalRecordSetting.setDoctorId(doctorId);
            emrMedicalRecordSetting.setType(type);
            emrMedicalRecordSetting.setName(e.getName());
            emrMedicalRecordSetting.setCreatedAt(new Date());
            emrMedicalRecordSetting.setChangedAt(new Date());
            if (Arrays.asList(typeArr).contains(type.toString())) {
                emrMedicalRecordSetting.setEnabled(MedicalRecordSettingEnum.ENABLE_YES);
            } else {
                emrMedicalRecordSetting.setEnabled(MedicalRecordSettingEnum.ENABLE_NO);
            }
            medicalRecordSettingList.add(emrMedicalRecordSetting);
        }
        this.medicalRecordSettingRepository.saveAll(medicalRecordSettingList);
    }
}
